home *** CD-ROM | disk | FTP | other *** search
/ Experimental BBS Explossion 3 / Experimental BBS Explossion III.iso / msdos / ctest259.zip / TIME.PAS < prev    next >
Pascal/Delphi Source File  |  1993-04-19  |  4KB  |  78 lines

  1. UNIT Time;   { Copyright (c) 1989-1993 Norbert Juffa }
  2.  
  3. INTERFACE
  4.  
  5. FUNCTION Clock: LONGINT;             { same as VMS; time in milliseconds }
  6.  
  7.  
  8. IMPLEMENTATION
  9.  
  10. FUNCTION Clock: LONGINT; ASSEMBLER;
  11. ASM
  12.              PUSH    DS              { save caller's data segment }
  13.              MOV     AX, 0040h       { set DS to BIOS data segment to }
  14.              MOV     DS, AX          {  access ticker counter }
  15.              MOV     BX, 6Ch         { offset of ticker counter in segm.}
  16.              MOV     DX, 43h         { timer chip control port }
  17.              MOV     AL, 4           { freeze timer 0 }
  18.              PUSHF                   { save caller's int flag setting }
  19.              CLI                     { make reading counter an atomic operation}
  20.              MOV     DI, DS:[BX]     { read BIOS ticker counter lo word }
  21.              MOV     CX, DS:[BX+2]   { read BIOS ticker counter hi word }
  22.              STI                     { enable update of ticker counter }
  23.              OUT     DX, AL          { latch timer 0 }
  24.              NOP                     { wait for }
  25.              NOP                     {  possible ticker }
  26.              NOP                     {   counter update }
  27.              NOP                     {    interrupt }
  28.              NOP                     {     to arrive }
  29.              CLI                     { make reading counter an atomic operation}
  30.              MOV     SI, DS:[BX]     { read BIOS ticker counter lo word }
  31.              MOV     BX, DS:[BX+2]   { read BIOS ticker counter hi word }
  32.              IN      AL, 40h         { read latched timer 0 lo-byte }
  33.              MOV     AH, AL          { save lo-byte }
  34.              IN      AL, 40h         { read latched timer 0 hi-byte }
  35.              POPF                    { restore caller's int flag }
  36.              XCHG    AL, AH          { correct order of hi and lo }
  37.              CMP     DI, SI          { ticker counter updated ? }
  38.              JE      @no_update      { no }
  39.              OR      AX, AX          { update before timer freeze ? }
  40.              JNS     @no_update      { no }
  41.              MOV     DI, SI          { use second }
  42.              MOV     CX, BX          {  ticker counter }
  43. @no_update:  NOT     AX              { counter counts down }
  44.              MOV     BX, 36EDh       { load multiplier }
  45.              MUL     BX              { W1 * M }
  46.              MOV     SI, DX          { save W1 * M (hi) }
  47.              MOV     AX, BX          { get M }
  48.              MUL     DI              { W2 * M }
  49.              XCHG    BX, AX          { AX = M, BX = W2 * M (lo) }
  50.              MOV     DI, DX          { DI = W2 * M (hi) }
  51.              ADD     BX, SI          { accumulate }
  52.              ADC     DI, 0           {  result }
  53.              XOR     SI, SI          { load zero }
  54.              MUL     CX              { W3 * M }
  55.              ADD     AX, DI          { accumulate }
  56.              ADC     DX, SI          {  result in DX:AX:BX }
  57.              MOV     DH, DL          { move result }
  58.              MOV     DL, AH          {  from DL:AX:BX }
  59.              MOV     AH, AL          {   to }
  60.              MOV     AL, BH          {    DX:AX:BH }
  61.              MOV     DI, DX          { save result }
  62.              MOV     CX, AX          {  in DI:CX }
  63.              MOV     AX, 25110       { calculate correction }
  64.              MUL     DX              {  factor }
  65.              SUB     CX, DX          { subtract correction }
  66.              SBB     DI, SI          {  factor }
  67.              XCHG    AX, CX          { result back }
  68.              MOV     DX, DI          {  to DX:AX }
  69.              POP     DS              { restore caller's data segment }
  70. END;
  71.  
  72.  
  73. BEGIN
  74.    Port [$43] := $34;                { need rate generator, not square wave }
  75.    Port [$40] := 0;                  { generator as programmed by some BIOSes }
  76.    Port [$40] := 0;                  { for timer 0 }
  77. END. { Time }
  78.